/*
*  <template slot="prefix" slot-scope="ref">
                    <a-button type="primary" icon="plus" @click="handleEdit(null,1)" v-btnPermission="'mm_004_add_01'">
                        新增
                    </a-button>
                </template>
* */
export default {
  name: 'BTable',
  props: {
    //是否显示分页
    showPage: {
      type: Boolean,
      default() {
        return true
      }
    },
    //分页的配置项，请求数据是会依照这个来传参
    pageKeys: {
      type: Array,
      default() {
        return ['pageNo', 'pageSize', 'totalSize']
      }
    },
    //选择的配置项，默认关闭，type可选为checkbox或radio，多选或者单选
    //注意：exportConfig.use为ture的话，会自动将selectConfig设置为{use: true, type: 'checkbox' }
    //如果点击事件没生效，那肯定是rowKey没设置对

    // :selectConfig = "{use: true, type: 'radio',rowKey: 'id' }"
    selectConfig: {
      type: Object,
      default() {
        return {
          use: false, //是否使用，传false不会显示选择栏
          type: 'checkbox', //checkbox或radio，多选或者单选
          rowKey: 'id'
        }
      }
    },
    //同a-table的columns，主要作用：div上不再显示[object Object],[object Object]...这种东西；次要作用：传值到a-table
    columns: {
      type: Array,
      required: true
    },
    //导出配置选择
    //:exportConfig="{ use: true,select: '导出选中',all: '导出全部'}"
    exportConfig: {
      type: Object,
      default() {
        return {
          use: false, //是否导出，传false不会显示操作栏
          select: '导出选中', //导出选中的文件名
          all: '导出全部', //导出全部的文件名
          customColumns: null //需要导出的表头,
        }
      }
    },
    //导出配置文字选择
    //:exportConfigText="{ select: '导出选中',all: '导出全部'}"
    exportConfigText: {
      type: Object,
      default() {
        return {
          select: '导出选中', //导出选中的文件名
          all: '导出全部' //导出全部的文件名
        }
      }
    },
    //导出权限配置选择
    //:exportPermission="{select: 'asdfa',all: 'asdfa'}"
    exportPermission: {
      type: Object,
      default() {
        return null
      }
    },
    //分页配置
    pageSizeOptions: {
      type: Array,
      default() {
        return ['10', '20', '30', '40', '100']
      }
    },
    /*
    如果不处理返回数据直接return 接口就可以了，如：parameter => getMonthlyReportList(Object.assign(parameter, this.queryParam))
    下面是要处理参数，然后还要包装返回数据的，有些后端瞎鸡儿返回的
    loadData: async parameter => {
        if (this.queryParam.createdTime && this.queryParam.createdTime.length > 0) {
          this.queryParam.evaluateStartTime = this.queryParam.createdTime[0].format('YYYY-MM-DD')
          this.queryParam.evaluateEndTime = this.queryParam.createdTime[1].format('YYYY-MM-DD')
          delete this.queryParam.createdTime
        }
        // this.getMonthlyReportsTotalReq()
        const requestParameters = Object.assign({}, parameter, this.queryParam)
        let res = await getMonthlyReportList({}, requestParameters)
        if (res.code === this.SUCCESS_CODE) {
          return { code: 200, ...res.data, data: res.data.list }
        }
        return { code: 200, data: [] }
    },
    * */
    //数据请求方法，返回值应该是一个promise
    request: {
      type: Function,
      // required: true,
      default() {
        return () => { }
      }
    },
    //:statisticsConfig = "{use: true,statistics}"
    statisticsConfig: {
      type: Object,
      default() {
        return {
          use: false, //是否统计，传false不会显示操作栏
          statistics: null,
          temp: null
        }
      }
    },
    outLoading: {
      type: Boolean,
      default: false
    },
    outSelectedRowKeys: {
      type: Array,
      default() {
        return []
      }
    },
    rowSelectionConfig: {
      type: Object,
      default() {
        return {}
      }
    },
    disabledLoading: {
      type: Boolean,
      default() {
        return false
      }
    },
    delFunc: {
      type: [Object, Function],
      default() {
        return null
      }
    },
    disabled: {
      type: Boolean,
      default() {
        return false
      }
    },
    transformTimeKey: {
      type: Array,
      default() {
        return []
      }
    },
    // 从表格第几列开始导出
    startIndex: {
      type: [Number, String],
      default() {
        return 1
      }
    },
    // 数据过滤器
    filterData: {
      type: Function,
      default() {
        return null
      }
    },
    isShowCountBar: {
      type: Boolean,
      default() {
        return null
      }
    },
    isShowTotal: {
      type: Boolean,
      default() {
        return true
      }
    },
    isShowDeleteCount: {
      type: Boolean,
      default() {
        return true
      }
    },
    size: {
      type: String,
      default: 'small'
    }
  },
  /*
   向上发射的事件
  * emit:{
      //行点击事件，回传的参数是点击event,和行数据
      row-click(event, record)，
      //选中框的事件，回传的是已选中的所有行。和row-click可同时绑定
      select-click(records)，
  * }
  * */
  data() {
    return {
      pathName: this.$route.path,
      innerLoading: false,
      loadingExportAll: false,
      //选中的key
      selectedRowKeys: [],
      pageNo: 1,
      pageSize: Number(this.pageSizeOptions[0]),
      totalSize: 0,
      tableData: [],
      selectedRowsMap: new Map()
    }
  },
  created() {
    if (!this.$route.params?.statisticsId) {  //表扬信管理模块bug修改
      this.getData()
    }
    console.log(this.$scopedSlots)

  },
  watch: {
    outLoading() {
      this.innerLoading = this.outLoading
    },
    outSelectedRowKeys: {
      immediate: true,
      handler() {
        this.selectedRowKeys = this.outSelectedRowKeys
      }
    },
    selectedRowKeys(newVal) {
      this.$emit('update:outSelectedRowKeys', newVal)
    }
  },
  methods: {
    /*
    * 删除方法，delFunc：对应的删除接口
    *
    * 使用例子：slot-scope="ref"里面的ref是回传的this对象，可以使用本组件methods里面的所有方法。
    *   <template :slot="state !== 3 ? 'prefix':''" slot-scope="ref">
            <a-button type="primary" @click="openDailog">添加行</a-button>
            <a-button @click="ref.delete(delFuc)">删除行</a-button>
        </template>
    * */
    delete(delFunc, callback) {
      if (delFunc) {
        this.$delList2(
          delFunc,
          async () => {
            if (this.totalSize - this.selectedRowKeys.length <= (this.pageNo - 1) * this.pageSize) {
              this.pageNo = this.pageNo - Math.round(this.selectedRowKeys.length / this.pageSize)
              this.pageNo = this.pageNo < 0 ? 0 : this.pageNo
            }
            // console.log(this.totalSize >= this.pageNo * this.pageSize)
            // console.log(this.pageNo)
            await this.getData()
            this.selectedRowKeys = []
            this.selectedRowsMap = new Map()
            callback && callback()
          },
          { ids: this.selectedRowKeys }
        )
      } else {
        this.$message.warning('请绑定删除方法')
      }
    },
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //notice:外部刷新数据，请这样使用getData(null , true)
    //获取数据
    async getData(callback, isReset = false, isClear = false) {
      this.tableData = []
      isClear && this.clearSelected()
      let page = {}
      page[this.pageKeys[0]] = this.pageNo
      page[this.pageKeys[1]] = callback ? this.totalSize : this.pageSize
      if (isReset) {
        page[this.pageKeys[0]] = this.pageNo = 1
      }
      // console.log(page)
      if (!this.disabledLoading) this.innerLoading = true
      try {
        let res = await this.request(page)
        // console.log('res',res)
        if (res.code === 200) {
          if (callback && res.data.length) {
            let filterData = this.filterData?.(res.data) ?? res.data
            callback(filterData)
            return (this.innerLoading = false)
          }
          this.tableData = res.data
          this.totalSize = res[this.pageKeys[2]]
        }
      } finally {
        this.innerLoading = false
      }
    },
    async getAllData() {
      return new Promise(async resolve => {
        let page = {}
        page[this.pageKeys[0]] = 1
        page[this.pageKeys[1]] = this.totalSize
        this.loadingExportAll = true
        let res = await this.request(page)
        this.loadingExportAll = false
        // console.log(res)
        if (res.code === 200) {
          resolve(res.data)
        } else {
          resolve([])
        }
      })
    },
    loadData() {
      this.getData(null, true, true)
    },
    refresh() {
      this.getData(null, true, true)
    },
    /*
     * 翻页或者改变页数，就更新pageNo和pageSize
     * */
    onShowSizeChange(current, size) {
      this.pageSize = size
      this.pageNo = current
      this.getData()
    },
    /*
     * 选中行
     * */
    onSelectChange(selectedRowKeys, selectedRows) {
      this.selectedRowKeys = selectedRowKeys
      this.selectedRowsMap.set(this.pageNo, selectedRows)
      if (this.selectConfig.type === 'radio') {
        this.$emit('row-click', null, selectedRows[0])
      } else {
        this.$emit('select-click', { rows: this.selectedRows(), keys: this.selectedRowKeys })
      }
      // console.log('onSelectChange',this.selectedRows())
    },
    /*导出表头*/
    exportHeader() {
      this.$refs.exportSelect.setDataAndGenerate([{}])
    },
    /*
     * 选择需要导出的数据
     * */
    exportSelect() {
      if (this.selectedRows().length > 0) {
        if (this.$listeners['exportSelect']) {
          return this.$emit('exportSelect', this.selectedRows())
        }
        let selectedRows = this.filterData?.(this.selectedRows()) ?? this.selectedRows()
        this.$refs.exportSelect.setDataAndGenerate(selectedRows)
      } else {
        this.$message.warning('请选择需要导出的数据')
      }
    },
    /*
     * 导出所有的数据
     * */
    async exportAll() {
      // 参数：查询条件、导出的回调
      if (this.totalSize) {
        if (this.$listeners['exportAll']) {
          return this.$emit('exportAll', await this.getAllData())
        }
        this.getData(this.$refs.exportAll.setDataAndGenerate, true)
      } else {
        this.$message.warning('没有可导出的数据')
      }
    },
    /*
     * 行选中
     * */
    rowClick(event, record) {
      if (record.disabled) return
      if (this.selectConfig.use && this.$listeners['row-click']) {
        if (this.selectConfig.rowKey === undefined) {
          this.selectConfig.rowKey = 'id'
        }
        if (this.selectConfig.type === 'checkbox') {
          let resIndex = this.selectedRowKeys.findIndex(v => v === record[this.selectConfig.rowKey])
          if (resIndex !== -1) {
            this.selectedRowKeys.splice(resIndex, 1)
          } else {
            this.selectedRowKeys.push(record[this.selectConfig.rowKey])
          }

          let pageNoRows = this.selectedRowsMap.get(this.pageNo)
          if (pageNoRows) {
            let resIndex2 = pageNoRows.findIndex(v => v.id === record[this.selectConfig.rowKey])
            if (resIndex2 !== -1) {
              pageNoRows.splice(resIndex2, 1)
            } else {
              pageNoRows.push(record)
            }
            this.selectedRowsMap.set(this.pageNo, pageNoRows)
          } else {
            this.selectedRowsMap.set(this.pageNo, [record])
          }
        } else {
          this.selectedRowKeys = [record[this.selectConfig.rowKey]]
          // this.selectedRows = [record]
        }
        this.$emit('row-click', event, record)
      }

      this.$emit('select-click', { rows: this.selectedRows(), keys: this.selectedRowKeys })
    },
    selectedRows() {
      let temp = []
      for (const values of this.selectedRowsMap.values()) {
        temp = temp.concat(values)
      }
      return temp
    },
    clearSelected() {
      this.selectedRowsMap.clear()
      this.selectedRowKeys = []
    }
  },
  mounted() {
    //如果不需要导出功能，那就不要初始化
    if (this.exportConfig.use) {
      const columns = this.exportConfig.customColumns // 需要导出的自定义表头，不存在则使用默认
      // console.log(columns)
      this.$refs.exportSelect.tableToExcelFile(columns ? { columns } : this.$refs.table, this.startIndex)
      this.$refs.exportAll.tableToExcelFile(columns ? { columns } : this.$refs.table, this.startIndex)
      this.selectConfig.use = true
      this.selectConfig.type = 'checkbox'
    }
    // let fixedColumns = this.columns.length && this.columns[this.columns.length-1],
    // fixedColumnsArr = ['operation','actions','action','operator']
    // if(fixedColumns.title=='操作' && fixedColumnsArr.includes(fixedColumns.dataIndex)){
    //   if(!fixedColumns.fixed){
    //     fixedColumns.fixed = "right";
    //   }
    // }
    // console.log('mounted-----------BBBBBBBBBBBBBBB-table的Path', this.pathName)
    // 监听详情页返回刷新列表
    this.$bus.$on('handleRefresh' + this.pathName, () => {
      // console.log('--------------------BBBBBBBBBBBBBBB-table收到了，刷新刷新刷新----------------', this.pathName)
      this.getData()
    })
  },
  beforeDestroy() {
    // console.log('beforeDestroy-------BBBBBBBBBBBBBBB-table的Path', this.pathName)
    this.$bus.$off('handleRefresh' + this.pathName)
  },
  render(createElement, context) {
    //操作栏，slot="prefix",slot="suffix",exportConfig.use = true任意一个存在的时候，就会显示
    //三个都不传就是一个纯表格，带翻页的
    let tableOperator = ''
    if (this.$scopedSlots.prefix || this.exportConfig.use || this.$scopedSlots.suffix) {
      //导出功能
      let actionBtn = (
        <div>
          {this.$scopedSlots.prefix && this.$scopedSlots.prefix(this)}
          {this.delFunc && !this.disabled ? (
            <a-button
              type="danger"
              disabled={this.selectedRowKeys?.length === 0}
              onClick={() => this.delete(this.delFunc)}
            >
              删除行
            </a-button>
          ) : (
            ''
          )}
          {this.exportConfig.use ? (
            this.exportPermission ? (
              <span>
                <excel
                  ref="exportSelect"
                  fileName={this.exportConfig.select}
                  transformTimeKey={this.transformTimeKey}
                  is-click-generate="false"
                >
                  <a-button
                    v-btn-permission={this.exportPermission.select}
                    icon="download"
                    type="primary"
                    slot="excelBtn"
                    disabled={this.selectedRowKeys?.length === 0}
                    onClick={this.exportSelect}
                  >
                    {this.exportConfigText.select}
                  </a-button>
                </excel>
                <excel
                  ref="exportAll"
                  fileName={this.exportConfig.all}
                  transformTimeKey={this.transformTimeKey}
                  is-click-generate="false"
                >
                  <a-button
                    v-btn-permission={this.exportPermission.all}
                    loading={this.loadingExportAll}
                    icon="download"
                    type="primary"
                    slot="excelBtn"
                    onClick={this.exportAll}
                  >
                    {this.exportConfigText.all}
                  </a-button>
                </excel>
              </span>
            ) : (
              <span>
                <excel ref="exportSelect" fileName={this.exportConfig.select} is-click-generate="false">
                  <a-button
                    icon="download"
                    type="primary"
                    slot="excelBtn"
                    disabled={this.selectedRowKeys?.length === 0}
                    onClick={this.exportSelect}
                  >
                    {this.exportConfigText.select}
                  </a-button>
                </excel>
                <excel ref="exportAll" fileName={this.exportConfig.all} is-click-generate="false">
                  <a-button
                    icon="download"
                    type="primary"
                    slot="excelBtn"
                    loading={this.loadingExportAll}
                    onClick={this.exportAll}
                  >
                    {this.exportConfigText.all}
                  </a-button>
                </excel>
              </span>
            )
          ) : (
            ''
          )}
          {this.$scopedSlots.suffix && this.$scopedSlots.suffix(this)}
        </div>
      )
      let isShowCountBar = false
      if (this.selectConfig.use) isShowCountBar = true
      if (this.statisticsConfig.use) isShowCountBar = true
      if (this.isShowCountBar !== null) isShowCountBar = this.isShowCountBar
      tableOperator = (
        <div class="table-operator">
          <div class="pub-table-action-btn">{actionBtn}</div>
          {this.$scopedSlots.bottom && this.$scopedSlots.bottom()}
          {isShowCountBar && (
            <a-alert class="mb12" type="info" show-icon>
              <template slot="message">
                {this.selectConfig.use && <span>已选择{this.selectedRowKeys.length}项&nbsp;&nbsp;&nbsp;</span>}
                {this.isShowTotal && <span>总计：{this.totalSize}&nbsp;&nbsp;&nbsp;</span>}
                {this.statisticsConfig.use ? (
                  this.statisticsConfig.temp ? (
                    this.statisticsConfig.temp(this.statisticsConfig.statistics)
                  ) : (
                    <span>
                      待提交审核：{this.statisticsConfig.statistics.draft || 0}， 审核中：
                      {this.statisticsConfig.statistics.submitted || 0}， 审核通过：
                      {this.statisticsConfig.statistics.past || 0}， 审核不通过：
                      {this.statisticsConfig.statistics.rejected || 0}
                      {this.isShowDeleteCount && <span>， 已作废：{this.statisticsConfig.statistics.delete || 0}</span>}
                    </span>
                  )
                ) : (
                  ''
                )}
              </template>
            </a-alert>
          )}
        </div>
      )
    }
    /*
    *
   <span>
                    &nbsp;&nbsp;&nbsp;待提交审核：{{ statistics.draft }}，
                    审核中：{{ statistics.submitted }}，
                    审核通过：{{ statistics.past }}，
                    审核不通过：{{ statistics.rejected }}，
                    已作废：{{ statistics.delete }}，
                    已变更：{{ statistics.change }}
                </span>
    *
    * */

    return (
      <div>
        {tableOperator}
        <a-table
          ref="table"
          row-key={this.selectConfig.rowKey}
          loading={this.innerLoading}
          dataSource={this.tableData}
          props={{ ...this.$attrs, ...this.$props }}
          scopedSlots={{ ...this.$scopedSlots }}
          row-selection={
            this.selectConfig.use
              ? Object.assign(
                {
                  selectedRowKeys: this.selectedRowKeys,
                  type: this.selectConfig.type,
                  onChange: this.onSelectChange,
                  getCheckboxProps: record => ({
                    props: { disabled: record.disabled }
                  })
                },
                this.rowSelectionConfig
              )
              : null
          }
          pagination={false}
          customRow={record => {
            return {
              on: {
                // 事件
                click: event => {
                  this.rowClick(event, record)
                } // 点击行
              }
            }
          }}
        >
        </a-table>
        {this.showPage && (
          <a-pagination
            style={{
              display: 'flex',
              'justify-content': 'flex-end',
              margin: '10px 0'
            }}
            current={this.pageNo}
            pageSize={this.pageSize}
            pageSizeOptions={this.pageSizeOptions}
            show-quick-jumper={true}
            showSizeChanger={true}
            total={this.totalSize}
            showTotal={(total, range) => `共 ${total} 条数据`}
            onShowSizeChange={this.onShowSizeChange}
            onChange={this.onShowSizeChange}
          ></a-pagination>
        )}
      </div>
    )
  }
}
